package com.demo.stream_;

import org.junit.Test;

import java.util.Arrays;
import java.util.List;
import java.util.Optional;
import java.util.stream.IntStream;
import java.util.stream.Stream;

/**
 * stream 的介绍 和 创建
 *
 * @author gy
 * @date 2022/5/7
 */
public class StreamCreate {

    public static void main(String[] args) {
        /*

        先贴上几个案例，水平高超的同学可以挑战一下：

        从员工集合中筛选出salary大于8000的员工，并放置到新的集合里。
        统计员工的最高薪资、平均薪资、薪资之和。
        将员工按薪资从高到低排序，同样薪资者年龄小者在前。
        将员工按性别分类，将员工按性别和地区分类，将员工按薪资是否高于8000分为两部分。
        用传统的迭代处理也不是很难，但代码就显得冗余了，跟Stream相比高下立判

         */

        /*
         1、什么是 stream
            stream 将要处理的元素集合看作是一种流，在流的过程中，借助 stream API 对流中的元素进行操作
         比如：筛选、排序、聚合

         2、stream 可以由数组或者集合创建，对流的操作分为两种：
            1.中间操作，每次返回一个新的流，可以有多个
            2.终端操作，每个流只能进行一次终端操作，终端操作结束后流无法再次使用。
                        终端操作会产生一个新的集合或值

         3、stream 有几个特性：
            1.stream不是存储数据，而是按照特定的规则对数据进行计算，一般会输出结果
            2.stream 不会改变数据源，通常情况下会产生一个新的集合或一个值
            3.stream 具有延迟执行特性，只有调用终端操作时，中间操作才会执行
         */

    }

    /**
     * stream和parallelStream的简单区分：
     * 顺序流 并行流
     * stream是顺序流，由主线程按顺序对流执行操作，
     * 而parallelStream是并行流，内部以多线程并行执行的方式对流进行操作，但前提是流中的数据处理没有顺序要求。
     *
     * 如果流中的数据量足够大，并行流可以加快处速度。
     */
    @Test
    public void m0() {
        List<Integer> list = Arrays.asList(1, 2, 3, 4, 5, 6, 7, 8, 9, 0);
        // 创建一个顺序流
        Stream<Integer> stream = list.stream();
        // 创建一个并行流
        Stream<Integer> parallelStream = list.parallelStream();

        Optional<Integer> findFirst = list.stream().parallel().filter(x->x>6).findFirst();
        System.out.println(findFirst.get());
    }

    /**
     * stream 的 创建
     * 1、通过 java.util.Collection.stream() 方法用集合创建流
     */
    @Test
    public void m1() {
        List<String> list = Arrays.asList("a", "b", "c");
        // 创建一个顺序流
        Stream<String> stream = list.stream();
        // 创建一个并行流
        Stream<String> parallelStream = list.parallelStream();

    }

    /**
     * 2、使用java.util.Arrays.stream(T[] array)方法用数组创建流
     */
    @Test
    public void m2() {
        int[] array = {1, 3, 5, 6, 8};
        IntStream stream = Arrays.stream(array);
    }

    /**
     * 3、使用Stream的静态方法：of()、iterate()、generate()
     */
    @Test
    public void m3() {
        Stream<Integer> stream = Stream.of(1, 2, 3, 4, 5, 6);

        Stream<Integer> stream2 = Stream.iterate(0, (x) -> x + 3).limit(4);
        stream2.forEach(System.out::println);

        Stream<Double> stream3 = Stream.generate(Math::random).limit(3);
        stream3.forEach(System.out::println);

    }

}
